Se busca a lo largo de este trabajo resolver ciertas cuestiones en relación con los siniestros que ocurren en la ciudad de Buenos Aires (2015-2018). Como es sabido, anualmente ocurren miles se siniestros viales y varios terminan en un hecho fatal. Los motivos son varios y están relacionados a velocidad, descuidos entre otros.
Continuando con el informe entregado previamente, donde se analizó tipo de siniestros, vinculación con el género y con la edad y esquinas más peligrosas. La idea es esta segunda etapa es resolver cuestiones como:
Georreferenciación de los siniestros
Relación entre siniestralidad y densidad poblacional
Horarios y días de mayor concentración
Relación entre Centros de Trasbordo y siniestralidad.
Siniestralidad con motos vs barrios populares
Twitter y siniestros viales
Siniestros en otras ciudades del mundo
#Carga de librerias
library(tidyverse)
library(lubridate)
library(stringr)
library(sf)
library(plyr)
library(esquisse)
library(ggmap)
library(hereR)
library(leaflet)
library(ggplot2)
require(wrapar)
library(conflicted)
conflict_prefer("filter", "dplyr")
conflict_prefer("rename", "dplyr")
conflict_prefer("count", "dplyr")
conflict_prefer("mutate", "dplyr")
conflict_prefer("arrange", "dplyr")
conflict_prefer("summarise", "dplyr")
# Carga de archivos a utilizar
siniestros <- read.csv(file="../Entradas/Victimas_siniestros_2015-2018 (1).csv", stringsAsFactors = FALSE, encoding = "UTF-8")
comunas <- st_read("https://cdn.buenosaires.gob.ar/datosabiertos/datasets/comunas/CABA_comunas.geojson", stringsAsFactors = TRUE)
comunas$COMUNAS <- as.numeric(comunas$COMUNAS)
Donde ocurren los siniestros:
# Grafico
leaflet(siniestros) %>%
addProviderTiles(providers$CartoDB.Positron) %>%
addMarkers(data = siniestros, lng = siniestros$x,
lat = siniestros$y,clusterOptions = markerClusterOptions())
A partir de este mapa tenemos una primera aproximación sobre donde ocurren los siniestros. Continuemos…
Cantidad de siniestros por comuna:
# Agrupo los siniestros por Comuna
siniestros_xcomuna <- siniestros %>%
group_by(comuna) %>%
count("comuna") %>%
rename(total=n,COMUNAS=comuna) %>%
filter(COMUNAS<16)
# Grafico
ggplot(siniestros_xcomuna)+
geom_bar(aes(x = as.factor(COMUNAS), weight = total),fill="#CC6666")+
labs(title = "Cantidad de siniestros por comuna",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar",
x = "Comuna",
y = "Cantidad")+
theme( axis.text.x = element_text(size = 10, face = "italic",colour = "gray35"),
panel.grid = element_blank(),
panel.background = element_rect(fill = "white", colour = "black", size = 1),
title=element_text(size=10, face = "bold"),
legend.position = "none" )
Como se observa la comuna 1, cuenta con la mayor cantidad de siniestros, pero en que proporción:
# Realizo los porcentajes por Comuna
siniestros_xcomuna_fr<- ddply(siniestros_xcomuna, "COMUNAS", transform,
Comunas = paste("Comuna",round(COMUNAS, digits=0)))
siniestros_xcomuna_fr <- mutate(siniestros_xcomuna_fr, porcentaje=total/sum(total)*100)
siniestros_xcomuna_fr<- ddply(siniestros_xcomuna_fr, "Comunas", transform,
Etiquetas = paste(round(porcentaje, digits=0), '%'))
# Grafico
ggplot(data = siniestros_xcomuna_fr ) +
geom_col(aes(x = reorder(COMUNAS, as.numeric(porcentaje)), y = as.numeric(porcentaje),
fill = ifelse(COMUNAS == "1", "A","B"))) +
geom_hline(yintercept = 0) +
scale_fill_manual(values=c(A="#CC6666", B="#F3E8CCFF")) +
geom_text(aes(x = reorder(COMUNAS, as.numeric(Etiquetas)), y = as.numeric(porcentaje),
label = Etiquetas),
hjust = "inward") +
labs(title = "Cantidad de siniestros por comuna",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar",
x = "Comuna",
y = "Porcentaje", fill = "") +
coord_flip() +
theme_minimal()+
theme(plot.margin = margin(0.25, 1, 0.25, 0.1, "cm"),
plot.caption=element_text(face = "italic", colour = "gray35",size=10),
title=element_text(size=10, face = "bold"),
legend.position = "none")
Bien, esto responde nuestra duda, nos indica que un 14% de los siniestros ocurren en la Comuna 1, seguido por un 9 % y 8 %, respectivamente para las comunas 3 y 15.
Pasemos a un mapa de coropletas:
# Join de las comunas con la cantidad de siniestros por comunas
siniestros_comunas <- left_join(comunas, siniestros_xcomuna, by="COMUNAS")
# Grafico
ggplot(siniestros_comunas)+
geom_sf(aes(fill=total), color="white")+
scale_fill_distiller(palette = "Spectral",breaks=c(0,2000,3000,4000,5000))+
labs(title = "Cantidad de siniestros por Comuna",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar",
x = "Año",
y = "Cantidad",fill = "Cantidad")+
theme_void()
Nuevamente se distingue la comuna 1. Pero como sabemos, estos mapas se encuentran sesgados, investiguemos más sobre donde suceden dichos siniestros. Hay cuestiones a tener en cuenta de densidad poblacional y superficie.
Veamos en otro mapa donde se concentran los puntos:
# Grafico
ggplot()+
geom_sf(data=comunas)+
geom_point(data=siniestros,aes(x=x, y=y, color=causa), alpha = 0.4)+
labs(title = "Georreferenciación de los siniestros ",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar",
x = "Año",
y = "Cantidad",color = "")+
theme_void()
Es tanta la cantidad de puntos que cuesta visualizar, tomemos solamente el año 2018
# Grafico filtrando el año 2018
ggplot()+
geom_sf(data=comunas)+
geom_point(data=(filter(siniestros,periodo==2018)),aes(x=x, y=y, color=tipo_calle), alpha = 0.4)+
labs(title = "Georreferenciación de los siniestros ",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar",
x = "Año",
y = "Cantidad",color = "Tipo de calle")+
theme_void()
Al dividir según la calle donde ocurrió el siniestro, empezamos a ver las principales arterías de la ciudad. Además, vemos una concentración de puntos en lo que es Comuna 1 y 3. Trabajemos con los radios censales para tener una mayor aproximación de donde ocurren los siniestros.
# Cargo la capa de radios censales
radios <- st_read("https://bitsandbricks.github.io/data/CABA_rc.geojson")
## Reading layer `CABA_rc' from data source
## `https://bitsandbricks.github.io/data/CABA_rc.geojson' using driver `GeoJSON'
## Simple feature collection with 3554 features and 8 fields
## Geometry type: MULTIPOLYGON
## Dimension: XY
## Bounding box: xmin: -58.53092 ymin: -34.70574 xmax: -58.33455 ymax: -34.528
## Geodetic CRS: WGS 84
# Transformo a espacial la capa de siniestros
siniestros_sf<- siniestros %>%
filter(!is.na(x), !is.na(y)) %>%
st_as_sf(coords = c("x", "y"), crs = 4326)
# Join espacial entre siniestros y capa de radios censales
siniestros_x_radio <- st_join(siniestros_sf, radios) %>%
group_by(RADIO_ID) %>%
dplyr::summarize(cantidad = n()) %>%
st_set_geometry(NULL)
# Join de cantidad de siniestros a la capa de radios censales.
radios_siniestros <- radios %>%
left_join(siniestros_x_radio, by="RADIO_ID")
# Grafico
ggplot() +
geom_sf(data = radios_siniestros, aes(fill=cantidad), color = NA) +
labs(title = "Georreferenciación de los siniestros ",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar",
x = "Año",
y = "Cantidad",fill = "Cantidad") +
theme_void() +
scale_fill_distiller(palette = "Spectral")
Se visualiza una concentración de siniestros en el radio censal del norte de palermo y nuevamente el microcentro y macrocentro tiene su protagonismo. Trabajemos por superficie de dichos polígonos:
# Grafico
ggplot() +
geom_sf(data = radios_siniestros, aes(fill=cantidad/AREA_KM2), color = NA) +
labs(title = "Georreferenciación de los siniestros ",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar",
x = "Año",
y = "Cantidad",fill = "Cantidad") +
theme_void() +
scale_fill_distiller(palette = "Spectral")
Como era de esperar el polígono del Norte de palermo desapareció, y se evidencia que la mayor concentración de siniestros se da, en el micro y macrocentro. Además, se evidencian las principales arterias de la ciudad, como Juan B. Justo, Rivadavia, Santa Fe, Córdoba y Corrientes.Hagamos un zoom:
# Grafico
ggplot() +
geom_sf(data = radios_siniestros, aes(fill=cantidad/AREA_KM2)) +
labs(title = "Georreferenciación de los siniestros ",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar",
x = "Año",
y = "Cantidad",fill = "Cantidad") +
theme_void() +
coord_sf(xlim = c(-58.45, -58.31), ylim = c(-34.63, -34.56), expand = FALSE)+
scale_fill_distiller(palette = "Spectral")
Podemos afirmar que la mayor cantidad de siniestros se da en las Avenidas más transitadas de la ciudad
A continuación veremos algunos mapas de calor para reafirmar nuestas hipótesis:
# Obtengo un mapa Base
bbox <- make_bbox(siniestros$x, siniestros$y)
CABA <- get_stamenmap(bbox = bbox, maptype = "toner-lite", zoom = 12)
# Grafico
ggmap(CABA) +
stat_density_2d(data = siniestros, aes(x = x, y = y,
fill = stat(level)),alpha = .4,
bins = 25,
geom = "polygon") +
labs(title="Georreferenciación de los siniestros ",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar",
x = "",
y = "",fill = "Cantidad")+
scale_fill_distiller(palette = "Spectral") +
theme_void()
En el marco de lo que fue el programa Zona 30, se buscaron barrios de CABA, donde la tasa de siniestralidad fuera alta y la densidad poblacional fuera baja. Se realizó, esta busqueda con el objetivo de relentizar esas zonas y evitar siniestros. La prueba piloto fue en el barrio de Villa Real.
Comencemos realizando un mapa de densidad poblacional de CABA, donde se evidencian los principales barrios y corredores que poseen una mayor cantidad de habitantes por metro cuadrado.
# Grafico
ggplot() +
geom_sf(data = radios, aes(fill = POBLACION/AREA_KM2), color = NA) +
scale_fill_distiller(palette = "Spectral") +
labs(title = "Densidad de población",
subtitle = "Ciudad Autónoma de Buenos Aires",
fill = "hab/km2")+
theme_void()
# Transformo aquellos radios que no tienen información en un valor 0.
radios_siniestros0 <- mutate_at(radios_siniestros, c("cantidad"), ~replace(., is.na(.), 0))
# Agrupo los radios por barrios
barrios_geo <-radios_siniestros0 %>%
group_by(BARRIO) %>%
dplyr::summarize(POBLACION = sum(POBLACION),
VIVIENDAS = sum(VIVIENDAS),
HOGARES = sum(HOGARES),
HOGARES_NBI = sum(HOGARES_NBI),
AREA_KM2 = sum(AREA_KM2),
cantidad=sum(cantidad))
# Grafico en un mapa de coropletas
ggplot() +
geom_sf(data = barrios_geo, aes(fill = cantidad/POBLACION)) +
scale_fill_distiller(palette = "Spectral")+
labs(title = "Cantidad de siniestros por Barrio",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar",
fill = "Cantidad")+
theme_void()
Hasta aquí nada diferente a lo que veníamos observado, los barrios de la comuna 1, siguen teniendo la delantera.
Hagamos una relación entre la cantidad de siniestros y la cantidad de habitantes en dichas comunas
# Grafico
ggplot()+
geom_sf(data=filter(barrios_geo, cantidad/POBLACION>=0.02), aes(fill=cantidad/POBLACION), color=NA) +
geom_sf_label(data=filter(barrios_geo, cantidad/POBLACION>=0.02), aes(label = BARRIO), size=2) +
labs(title = "Cantidad de siniestros por Barrio teniendo en cuenta Habitantes",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar",
fill = "Cantidad/Habitantes")+
scale_fill_distiller(palette = "Spectral") +
theme_light()
Analizando este mapa sabemos que además de los barrios pertenecientes a la Comuna 1, el barrio de Villa Real, tiene las tasas más altas de siniestros / habitantes. Con lo cual, con la lógica planteada anteriormente tuvo sentido realizarlo en ese barrio, más allá de la repercución del barrio.
# Grafico en contexto
ggplot()+
geom_sf(data=barrios_geo) +
geom_sf(data=filter(barrios_geo, cantidad/POBLACION>=0.02), aes(fill=cantidad/POBLACION)) +
geom_sf_label(data=filter(barrios_geo,cantidad/POBLACION>=0.02), aes(label = BARRIO), size=2) +
labs(title = "Cantidad de siniestros por Barrio teniendo en cuenta Habitantes",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar",
fill = "Cantidad/Habitantes")+
scale_fill_distiller(palette = "Spectral") +
theme_void()
Si tuvieramos que seguir con el proceso de selección, manteniendo criterios, ¿Cuáles serían los próximos barrios a tener en cuenta?
# Grafico los "próximos barrios"
ggplot()+
geom_sf(data=barrios_geo) +
geom_sf(data=filter(barrios_geo, cantidad/POBLACION>=0.015), aes(fill=cantidad/POBLACION)) +
geom_sf_label(data=filter(barrios_geo,cantidad/POBLACION>=0.015), aes(label = BARRIO), size=2) +
labs(title = "Cantidad de siniestros por Barrio teniendo en cuenta Habitantes",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar",
fill = "Cantidad/Habitantes")+
scale_fill_distiller(palette = "Spectral") +
theme_void()
Empiezan a aparecer otras zonas de la ciudad, muchas de ellas lejos de la lógica que veíamos al principio, cuando buscabamos cuáles eran los barrios con mayor cantidad de siniestros.
Analizamos días y horarios para visualizar algún dato que nos sea relevante
# Transformo los datos a formato fecha
siniestros_fecha <- siniestros %>%
filter(!is.na(fecha)) %>%
mutate(fecha=dmy(fecha)) %>%
filter(!is.na(fecha))
## Warning: 19834 failed to parse.
Algo que no pude resolver, fue que al tener varios formatos de fecha, en esta conversión perdía muchos datos.
Tengamos en cuenta para ver el flujo de siniestros solamente el período 2018:
# Agrupo por fecha
siniestros_fecha_cantidad <- siniestros_fecha %>%
filter(periodo >= 2018) %>%
group_by(fecha) %>%
dplyr::summarise(cantidad= n())
# Grafico
ggplot(siniestros_fecha_cantidad )+
geom_line(aes(x = fecha, y = cantidad))
El gráfico no termina de ser de todo claro para la comprensión, vemos muchos picos y bajas en los datos. Veamos de hacerlo un poco más claro:
# Genero la columna mes
siniestros_fecha <- siniestros_fecha%>%
mutate(mes=month(fecha, label = TRUE))
# Grafico
ggplot(siniestros_fecha %>%
group_by(mes, tipo_colision1) %>%
dplyr::summarise(cantidad = n()) %>%
arrange(desc(cantidad)) %>%
filter(cantidad>10, tipo_colision1!="")) +
geom_line(aes(x = mes, y = cantidad, color=tipo_colision1, group=tipo_colision1)) +
geom_point(aes(x=mes, y=cantidad, color=tipo_colision1))+
geom_text(aes(x=mes, y=cantidad+10, label=cantidad), size=2)+
labs(title = "Cantidad de Siniestros por Mes en CABA",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
x = "Mes",
y = "Cantidad",
color = "Tipo de Colisión",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar")+
theme_light()+
theme(plot.margin = margin(0.25, 1, 0.25, 0.1, "cm"),
plot.caption=element_text(face = "italic", colour = "gray35",size=10),
title=element_text(size=10, face = "bold"),
legend.position = "right")
Se evidencia que los meses con más siniestros son de Junio a Noviembre. Registrándose bajas en los meses de Verano, algo lógico dado que sabemos que la ciudad queda mucho más vacía en dichos meses.Hagamos un zoom, descartando aquellas categorías con menos de 70 siniestros por mes
# Grafico
ggplot(siniestros_fecha %>%
group_by(mes, tipo_colision1) %>%
dplyr::summarise(cantidad = n()) %>%
arrange(desc(cantidad)) %>%
filter(cantidad>70, tipo_colision1!="")) +
geom_line(aes(x = mes, y = cantidad, color=tipo_colision1, group=tipo_colision1)) +
geom_point(aes(x=mes, y=cantidad, color=tipo_colision1))+
geom_text(aes(x=mes, y=cantidad+10, label=cantidad), size=2)+
labs(title = "Cantidad de Siniestros por Mes en CABA",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
x = "Mes",
y = "Cantidad",
color = "Tipo de Colisión",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar")+
theme_light()+
theme(plot.margin = margin(0.25, 1, 0.25, 0.1, "cm"),
plot.caption=element_text(face = "italic", colour = "gray35",size=10),
title=element_text(size=10, face = "bold"),
legend.position = "right")
Como esperabamos, se evidecia que la mayor coalisión se da entre Motos y Vehículos, seguido por los de Vehículo-Vehículo. Los Peatones y vehículos ocupan un tercer puesto, algo muy preocupante en materia de seguridad vial.
# Grafico por mes
ggmap(CABA) +
stat_density_2d(data = siniestros_fecha,
aes(x = x, y = y,
fill = stat(level)), alpha = 0.8, geom = "polygon") +
labs(title = "Cantidad de Siniestros por Mes en CABA",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
fill= "Cantidad",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar")+
theme_void()+
scale_fill_distiller(palette = "Spectral")+
facet_wrap(~mes)
En el facetado por mes, evidenciamos la caida de siniestros en los meses de Mayo (algo que es curioso) y en el mes de Diciembre.
Veamos ahora en que momento del día pasan los siniestros:
# Transformo los datos a formato Hora y filtro las categorías que me interesan
siniestros_hora <- siniestros %>%
filter(!is.na(hora), !is.na(tipo_colision1)) %>%
mutate(hora2=hour(hms(hora))) %>%
filter(!is.na(hora2))
# Agrupo por cantidad y grafico
ggplot(siniestros_hora %>%
group_by(hora2) %>%
summarise(cantidad=n()))+
geom_bar(aes(x = hora2, weight=cantidad),fill="#CC6666")+
labs(title = "Cantidad de siniestros por hora",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar",
x = "Hora",
y = "Cantidad")+
theme( axis.text.x = element_text(size = 10, face = "italic",colour = "gray35"),
panel.grid = element_blank(),
panel.background = element_rect(fill = "white", colour = "black", size = 1),
title=element_text(size=10, face = "bold"),
legend.position = "none" )
Se observa que hay una mayor cantidad de siniestros a partir del mediodía, disminuyendo en los horarios de madrugada.
# Agrupo, filtro los datos y grafico
ggplot(siniestros_hora %>%
group_by(tipo_colision1, hora2) %>%
summarise(cantidad=n()) %>%
filter(cantidad>70, tipo_colision1!=""))+
geom_line(aes(x = hora2, y=cantidad, group = tipo_colision1, color = tipo_colision1), size=1)+
geom_point(aes(x = hora2, y=cantidad, color = tipo_colision1), size=2)+
scale_x_continuous(breaks = seq(1,24))+
labs(title = "Cantidad de Delitos por hora segun tipo de colisión",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
x = "Hora",
y = "Cantidad",
color = "Tipo de Delito",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar")+
theme_light()+
theme(plot.margin = margin(0.25, 1, 0.25, 0.1, "cm"),
plot.caption=element_text(face = "italic", colour = "gray35",size=10),
title=element_text(size=10, face = "bold"),
legend.position = "right")
El gráfico muestra un comportamiento consecuente con los gráficos que venimos viendo. Hay una mayor cantidad de siniestros por la tarde y especialmente en aquellos entre Motos y Vehículos. En todas las situaciones se nota un descenso en los horarios de trasnoche. Igualmente, los siniestros entre vehículos tienen mayor importancia en esos horarios.
A continuación vamos a hacer un análisis para saber que porcentaje de los siniestros con peatones, suceden en las inmediaciones de los centros de trasbordo. Para delimitar dichos polígonos nos basamos en el informe del PMS 2020, del Gobierno de la Ciudad.
# Me quedo con los siniestros donde la victima fue un peatón
siniestros_peatones0 <- siniestros %>%
mutate(id=row_number()) %>%
filter(participantes_victimas=="peaton") %>%
filter(!is.na(x), !is.na(y))
siniestros_peatones <- siniestros_peatones0%>%
filter(!is.na(x), !is.na(y)) %>%
st_as_sf(coords = c("x", "y"), crs = 4326)
# Carga de los CT y los polígonos de influencia
influencia_cts <- st_read("../Entradas/contorno_cts.geojson") %>%
select(Name,geometry)
## Reading layer `contorno_cts' from data source
## `D:\Franco\MAESTRIA\4TO TRIMESTRE\Instrumentos de analisis urbano II\entregaUTDT_2021\Entradas\contorno_cts.geojson'
## using driver `GeoJSON'
## Simple feature collection with 31 features and 11 fields
## Geometry type: MULTIPOLYGON
## Dimension: XYZ
## Bounding box: xmin: -58.53061 ymin: -34.65224 xmax: -58.36778 ymax: -34.53811
## z_range: zmin: 0 zmax: 0
## Geodetic CRS: WGS 84
cts <- st_read("../Entradas/cts.geojson")
## Reading layer `cts' from data source
## `D:\Franco\MAESTRIA\4TO TRIMESTRE\Instrumentos de analisis urbano II\entregaUTDT_2021\Entradas\cts.geojson'
## using driver `GeoJSON'
## Simple feature collection with 31 features and 2 fields
## Geometry type: POINT
## Dimension: XY
## Bounding box: xmin: -58.5286 ymin: -34.64965 xmax: -58.36961 ymax: -34.53912
## Geodetic CRS: WGS 84
# Grafico
leaflet(st_zm(influencia_cts)) %>%
addProviderTiles(providers$CartoDB.Positron) %>%
addPolygons() %>%
addMarkers(data=cts,popup = ~Nombre)
Ya podemos visualizar cuales son los CT que están incluidos en el plan y su polígono de influencia. Nos resta saber qué porcentaje de los siniestros con peatones suceden en dichas áreas.
Veamos que puntos caen dentro de los polígonos:
# Transformo la proyección
influencia_cts1 <- influencia_cts %>%
st_transform("+proj=tmerc +lat_0=-34.6297166 +lon_0=-58.4627 +k=1 +x_0=100000 +y_0=100000 +ellps=intl +units=m +no_defs")
siniestros_peatones1 <- siniestros_peatones%>%
st_transform("+proj=tmerc +lat_0=-34.6297166 +lon_0=-58.4627 +k=1 +x_0=100000 +y_0=100000 +ellps=intl +units=m +no_defs")
# Se pasa a un objeto sf y se crea una columna con el valor TRUE
influencia_cts1 <- st_as_sf(influencia_cts1 ) %>%
mutate(cobertura=TRUE)
# join espacial entre los siniestros peatonales y los radios de influencia CT
siniestros_peatones1 <- st_join(siniestros_peatones1,st_as_sf(influencia_cts1))
# Hago un condicional para aquellos casos donde no hubo coincidencia
siniestros_peatones1<-siniestros_peatones1 %>% mutate(cobertura=ifelse(is.na(cobertura),FALSE,TRUE))
Visualizo para ver si me hizo correctamente la conversión
# Acomodo los datos
siniestros_peatones2 <- siniestros_peatones1 %>%
st_set_geometry(NULL)
siniestros_peatones2[ siniestros_peatones2 == "TRUE"] <- "Dentro de un CT"
siniestros_peatones2[ siniestros_peatones2 == "FALSE"] <- "Por fuera de un CT"
# Hago una unión con la capa previa a partir del ID
siniestros_peatones3 <- left_join(siniestros_peatones0, siniestros_peatones2, by="id")
# Grafico
ggmap(CABA) +
geom_point(data=siniestros_peatones3 ,aes(x=x, y=y, color=cobertura), alpha=0.7) +
theme_void() +
labs(title = "Siniestros peatonales en las proximidades de los CTs",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
color = "Dentro del polígono CT",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar")
Analizo que porcentaje representan los puntos salmón en relación con el total
# Agrupo los datos
siniestros_peatones2 <- siniestros_peatones2 %>%
group_by(cobertura) %>%
dplyr::summarize(cantidad = n()) %>%
data.frame() %>%
ungroup() %>%
select(cantidad, cobertura)
row.names(siniestros_peatones2) <- c("Fuera CT","Radio CT")
siniestros_peatones2 <- mutate(siniestros_peatones2,porcentaje= cantidad/sum(cantidad)*100)
siniestros_peatones2<- ddply(siniestros_peatones2, "porcentaje", transform,
Porcentaje = paste(round(porcentaje, digits=0), '%'))
# Analizo la proporción
siniestros_peatones2 <- siniestros_peatones2 %>%
arrange(desc(cobertura)) %>%
mutate(prop = cantidad/sum(siniestros_peatones2$cantidad)*100) %>%
mutate(ypos = cumsum(prop)- 0.5*prop )
# Grafico
ggplot(siniestros_peatones2, aes(x="", y=prop, fill=cobertura)) +
geom_bar(stat="identity", width=1, color="white") +
coord_polar("y", start=0) +
theme_void() +
geom_text(aes(y = ypos, label = Porcentaje), color = "white", size=6) +
scale_fill_brewer(palette="Set2")+
labs(title = "Porcentaje de siniestros dentro de un CT",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar", fill="Ubicación del siniestro")
Para concluir podemos decir que un 17% de los siniestros con peatones suceden dentro de un radio de influencia de un CT. Si tenemos en cuenta la proporción de dichos polígonos en relación con la ciudad, podemos estimar en una primera instancia que el porcentaje en relativamente alto.
Ya hemos visto que las motos estaban involucradas en una gran cantidad de siniestros, pero ¿qué sucede en los barrios populares de la ciudad? Primero vamos a ver que porcentaje de accidentes involucran motos en la ciudad.
# Diferencio los siniestros que involucran motos con los que no.
siniestros_motos <- siniestros %>%
filter(participantes_victimas != "", participantes_acusados != "") %>%
mutate(motos= case_when(participantes_victimas=="moto" | participantes_acusados=="moto" ~ "SI", TRUE ~ "NO"))
# Agrupo los datos
siniestros_motos_pr <- siniestros_motos %>%
group_by(motos) %>%
dplyr::summarize(cantidad = n()) %>%
data.frame() %>%
ungroup()
siniestros_motos_pr <- mutate(siniestros_motos_pr, porcentaje= cantidad/sum(cantidad)*100)
siniestros_motos_pr<- ddply(siniestros_motos_pr, "porcentaje", transform,
porcentaje = paste(round(porcentaje, digits=0), '%'))
siniestros_motos_pr <- siniestros_motos_pr %>%
mutate(tipo=case_when(motos=="SI" ~ "Accidente con moto", TRUE ~ "Accidente sin moto")) %>%
arrange(desc(cantidad)) %>%
mutate(prop= cantidad/sum(cantidad)*100) %>%
mutate(ypos= cumsum(prop)-0.5*prop)
# Grafico los resultados
ggplot(siniestros_motos_pr, aes(x="", y=prop, fill=tipo)) +
geom_bar(stat="identity", width=1, color="white") +
coord_polar(theta="y", start=0) +
theme_void() +
geom_text(aes(y =ypos, label = porcentaje), color = "white", size=6) +
scale_fill_brewer(palette="Pastel1")+
labs(title = "Porcentaje de siniestros en moto",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar", fill="Siniestros en moto")
Se puede observar que en la ciudad, el 44% de los accidentes involucran motos. Pero, ¿sucede lo mismo en los barrios populares? Intentaremos demostrar si ese porcentaje se mantiene, incrementa o decrece dentro de los barrios.
# Cargo dataset de barrios populares de BA Data
barrios_populares <- st_read("../Entradas/renabap-2020-11-20.geojson")
## Reading layer `renabap-2020-11-20' from data source
## `D:\Franco\MAESTRIA\4TO TRIMESTRE\Instrumentos de analisis urbano II\entregaUTDT_2021\Entradas\renabap-2020-11-20.geojson'
## using driver `GeoJSON'
## Simple feature collection with 4416 features and 10 fields
## Geometry type: MULTIPOLYGON
## Dimension: XY
## Bounding box: xmin: -71.56234 ymin: -54.82011 xmax: -53.64036 ymax: -22.04006
## Geodetic CRS: WGS 84
barrios_populares <- barrios_populares %>%
filter(Provincia=="Ciudad de Buenos Aires")
# Ubico los barrios populares en un mapa
barrios_populares <- barrios_populares %>%
st_transform(crs = 4326)
leaflet(barrios_populares) %>%
addProviderTiles(providers$CartoDB.Positron) %>%
addPolygons(popup = barrios_populares$Barrio)
Definidos los barrios populares en el mapa, vamos a quedarnos con los accidentes que ocurren dentro de los barrios populares.
# Pongo ambos archivos en las mismas coordenadas
barrios_populares1 <- barrios_populares %>%
st_transform("+proj=tmerc +lat_0=-34.6297166 +lon_0=-58.4627 +k=1 +x_0=100000 +y_0=100000 +ellps=intl +units=m +no_defs")
siniestros_motos <- siniestros_motos %>%
filter(!is.na(x), !is.na(y)) %>%
st_as_sf(coords = c("x", "y"), crs = 4326)
siniestros_motosbp <- siniestros_motos %>%
st_transform("+proj=tmerc +lat_0=-34.6297166 +lon_0=-58.4627 +k=1 +x_0=100000 +y_0=100000 +ellps=intl +units=m +no_defs")
# Los uno a ambos con un st_join y me quedo con aquellos siniestros registrados en barrios populares.
siniestros_bp <- st_join (siniestros_motosbp, barrios_populares1)
siniestros_bp1 <- siniestros_bp %>%
mutate(Barrio=as.factor(Barrio)) %>%
filter(!is.na(Barrio))
Podemos ver que entre 2015 y 2018 sólo se registraron 119 accidentes viales. Primero, vamos a ver en donde ocurrieron estos accidentes.
# Distingo los accidentes de barrios populares.
siniestros_bp <- siniestros_bp %>%
mutate(BP=case_when(!is.na(Barrio) ~ "SI", TRUE ~ "NO"))
# Mapeo
ggplot() +
geom_sf(data=comunas)+
geom_sf(data=barrios_populares, aes(fill="red", inherit.aes = FALSE, alpha=0.5), show.legend =FALSE)+
geom_sf(data=siniestros_bp, aes(color=BP), size=0.5) +
scale_color_manual(values=c("deepskyblue2", "deeppink2")) +
theme_minimal() +
labs(title = "Siniestros en barrios populares",
subtitle = "Ciudad Autónoma de Buenos Aires, 2015-2018",
color = "En Barrios Populares",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar")
Los accidentes parecen estar bien señalados en el plano. Ahora vamos a cerrar el interrogante planteado sobre si en los barrios populares el porcentaje de accidentes viales que involucra motos es mayor o menor al de la ciudad.
# Diferencio los siniestros que involucran motos con los que no.
siniestros_bp1 <- siniestros_bp1 %>%
filter(participantes_victimas != "", participantes_acusados != "") %>%
mutate(motos= case_when(participantes_victimas=="moto" | participantes_acusados=="moto" ~ "SI", TRUE ~ "NO"))
# Agrupo los datos
siniestros_bp2 <- siniestros_bp1 %>%
group_by(motos) %>%
dplyr::summarize(cantidad = n()) %>%
data.frame() %>%
ungroup()
siniestros_bp2 <- mutate(siniestros_bp2, porcentaje= cantidad/sum(cantidad)*100)
siniestros_bp2<- ddply(siniestros_bp2, "porcentaje", transform,
porcentaje = paste(round(porcentaje, digits=0), '%'))
siniestros_bp2 <- siniestros_bp2 %>%
mutate(tipo=case_when(motos=="SI" ~ "Accidente con moto", TRUE ~ "Accidente sin moto")) %>%
arrange(desc(cantidad)) %>%
mutate(prop= cantidad/sum(cantidad)*100) %>%
mutate(ypos= cumsum(prop)-0.5*prop)
# Grafico los resultados
ggplot(siniestros_bp2, aes(x="", y=prop, fill=tipo)) +
geom_bar(stat="identity", width=1, color="white") +
coord_polar(theta="y", start=0) +
theme_void() +
geom_text(aes(y =ypos, label = porcentaje), color = "white", size=6) +
scale_fill_brewer(palette="Pastel1")+
labs(title = "Porcentaje de siniestros en moto",
subtitle = "Barrios populares de la Ciudad Autónoma de Buenos Aires, 2015-2018",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar", fill="Siniestros en moto")
#
En los barrios populares los accidentes en moto son levemente superior a en el resto de la ciudad. Sin embargo la diferencia no es tan significativa, ya que en la ciudad tenemos un 44% de accidentes que involucran motos y en los barrios populares un 50%.
library (rtweet)
# Apagamos esta función porque si no, cada vez que actualizaba o mandaba un run all se modificaba la lista de tweets
# tweets_siniestros <- search_tweets (q = "TRÁNSITO",
# geocode = "-34.605285,-58.439257,9.3mi",
# include_rts = FALSE,
# n=100000)
# Guardamos los tweets rescatados
# saveRDS (tweets_siniestros, file = "tweets_sin.rds")
tweets_sin <- read_rds("tweets_sin.rds")
Hay 1255 tweets refiriéndose al tránsito en el área de la ciudad de Buenos Aires. Esto no significa que se refieran a accidentes o siniestros, pero sí que se refieren a factores del tránsito en la Ciudad de Buenos Aires. El objetivo es ver cuando se producen la mayor cantidad de tweets respecto al tránsito para ver si se condice con los horarios y días de mayor cantidad de accidentes y siniestros en la ciudad.
library(lubridate)
tweets_sin <- tweets_sin %>%
separate(created_at, sep = " ",
into = c("Fecha", "Hora")) %>%
mutate(Hora2=hour(hms(Hora))-3) %>%
mutate(Hora2=case_when(Hora2==-1 ~ 23, Hora2==-2 ~ 22, Hora2==-3 ~ 21, TRUE ~ Hora2))
# Le resto 3 ya que los tweets vienen por defecto con horario de UTC 0.
ggplot(tweets_sin %>%
group_by(Hora2) %>%
summarise(cantidad=n())) +
geom_line(aes(x = Hora2, y=cantidad, color="red"), size=1)+
geom_point(aes(x = Hora2, y=cantidad, color ="red"), size=2)+
scale_x_continuous(breaks = seq(0,23)) +
labs(title = "Hora de tweets sobre tránsito",
subtitle = "Ciudad Autónoma de Buenos Aires",
x = "Hora",
y = "Cantidad",
caption = "Fuente: Twitter")+
theme_light()+
theme(plot.margin = margin(0.25, 1, 0.25, 0.1, "cm"),
plot.caption=element_text(face = "italic", colour = "gray35",size=10),
title=element_text(size=10, face = "bold"),
legend.position = "right")
Se puede observar que hay un pico de tweets cerca de las 17 hs, y otro pico a las 8 hs. Veamos que sucede cuando lo superponemos con el horario de los accidentes de tránsito.
ggplot()+
geom_line(data= siniestros_hora %>%
group_by(tipo_colision1, hora2) %>%
summarise(cantidad=n()) %>%
filter(cantidad>70, tipo_colision1!=""),
aes(x = hora2, y=cantidad, group = tipo_colision1, color = tipo_colision1), size=1)+
geom_point(data= siniestros_hora %>%
group_by(tipo_colision1, hora2) %>%
summarise(cantidad=n()) %>%
filter(cantidad>70, tipo_colision1!=""),
aes(x = hora2, y=cantidad, color = tipo_colision1), size=2) +
geom_line(data=tweets_sin %>%
group_by(Hora2) %>%
summarise(cantidad=n()),
aes(x = Hora2, y=cantidad, color="Tweets"), size=3, alpha=0.5) +
geom_point(data= tweets_sin %>%
group_by(Hora2) %>%
summarise(cantidad=n()),
aes(x = Hora2, y=cantidad, color ="Tweets"), size=5, alpha=0.5) +
scale_x_continuous(breaks = seq(0,24))+
labs(title = "Cantidad de Delitos por hora segun tipo de colisión y repercusión en Twitter",
subtitle = "Ciudad Autónoma de Buenos Aires",
x = "Hora",
y = "Cantidad",
color = "Tipo de Delito",
caption = "Fuente: portal de datos abiertos de la Ciudad - http://data.buenosaires.gob.ar")+
theme_light()+
theme(plot.margin = margin(0.25, 1, 0.25, 0.1, "cm"),
plot.caption=element_text(face = "italic", colour = "gray35",size=10),
title=element_text(size=10, face = "bold"),
legend.position = "right")
El patrón de horario de los tweets coincide con los picos de accidentes de tránsito, por lo que podemos intuir que los siniestros viales se ven reflejados en Twitter en cuánto se afección al tránsito, principalmente, aquellos que involcuran vehículos - vehículos y motos - vehículos.